﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Interface;

namespace Model
{
    public class ClsPumpeCol
    {
        public List<ClsPumpe> Pumper { get; private set; }
        object Lås;
        IClsController C;

        public ClsPumpeCol(IClsController C)
        {
            this.C = C;
            this.Pumper = new List<ClsPumpe>();
            this.Lås = new object();
        }

        public void TilføjPumpe(int Id, string Beliggenhed, double KvadratmeterVandSekundet, IClsKanal FraKanal, IClsKanal TilKanal)
        {
            lock (this.Lås)
            {
                this.Pumper.Add(new ClsPumpe(Id, KvadratmeterVandSekundet, FraKanal, TilKanal));
            }
        }

        public void TilpasPumper(double Ændring, IClsKanal FraKanal)
        {
            List<ClsPumpe> KanalPumper = this.Pumper.Where(val => val.Fra == FraKanal && val.Defekt == false).ToList();
            KanalPumper = KanalPumper.OrderBy(val => val.Til.SidsteVandstand).ThenByDescending(val => val.KvadratmeterVandSekundet).ToList();
            
            double KvadratmeterVandSekundet = KanalPumper
                .Where(val => val.On)
                .Sum(val => val.KvadratmeterVandSekundet)
                + Ændring;
            
            double Sum = KanalPumper.Sum(val => val.KvadratmeterVandSekundet);
            if(KvadratmeterVandSekundet >= Sum)
            {
                StartAlle(FraKanal);
            }
            else if (KvadratmeterVandSekundet > 0)
            {
                foreach (ClsPumpe P in KanalPumper)
                {
                    Sum -= P.KvadratmeterVandSekundet;

                    if (P.KvadratmeterVandSekundet <= KvadratmeterVandSekundet || Sum <= KvadratmeterVandSekundet)
                    {
                        //Start
                        if (P.On == false)
                        {
                            if (this.C.StartPumpe(P.Id))
                            {
                                KvadratmeterVandSekundet -= P.KvadratmeterVandSekundet;
                                this.C.Write("Pumpe Tændt: " + P.Id + " - Kvadratmeter Vand i Sekundet: " + P.KvadratmeterVandSekundet + "m^3");
                            }
                        }
                    }
                    else
                    {
                        //Sluk
                        if (P.On)
                        {
                            if (this.C.SlukPumpe(P.Id))
                            {
                                this.C.Write("Pumpe slukket: " + P.Id + " - Kvadratmeter Vand i Sekundet: " + P.KvadratmeterVandSekundet + "m^3");
                            }
                        }
                    }
                }
                this.C.Write("Mangler: " + KvadratmeterVandSekundet);
            }
            else
                this.C.Write("Ingen ændring i kanal "+ FraKanal.Id);
        }

        public void StartAlle(IClsKanal Kanal)
        {
            lock (this.Lås)
            {
                foreach (ClsPumpe P in this.Pumper.Where(val => val.Defekt == false && val.Fra == Kanal))
                {
                    this.C.StartPumpe(P.Id);
                }

                this.C.Write("Alle pumper startet");
            }
        }

        public void SlukAlle(IClsKanal Kanal)
        {
            lock (this.Lås)
            {
                foreach (ClsPumpe P in this.Pumper.Where(val => val.Defekt == false && val.Fra == Kanal))
                {
                    this.C.SlukPumpe(P.Id);
                }
            }
        }

        public void DefektPumpe(int Id)
        {
            ClsPumpe P = this.Pumper.SingleOrDefault(val => val.Id == Id);

            if (P != null)
            {
                lock (this.Lås)
                {
                    P.Defekt = true;
                    P.Sluk();
                    TilpasPumper(P.KvadratmeterVandSekundet, P.Fra);
                }
            }
        }

        public void ReparerPumpe(int Id)
        {
            ClsPumpe P = this.Pumper.SingleOrDefault(val => val.Id == Id);

            if (P != null)
            {
                lock (this.Lås)
                {
                    P.Defekt = false;
                }
            }
        }

        public void StartPumpe(int Id)
        {
            ClsPumpe P = this.Pumper.SingleOrDefault(val => val.Id == Id);

            if (P != null)
                P.Start();
        }

        public void SlukPumpe(int Id)
        {
            ClsPumpe P = this.Pumper.SingleOrDefault(val => val.Id == Id);

            if (P != null)
                P.Sluk();
        }
    }
}
